home *** CD-ROM | disk | FTP | other *** search
/ PD Collection CD 1 / PD Collection CD 1.iso / textual / tex / files / !preview / RCS / c / output < prev    next >
Encoding:
Text File  |  1990-07-27  |  9.2 KB  |  397 lines

  1. head     1.3;
  2. branch   ;
  3. access   ;
  4. symbols  ;
  5. locks    gtoal:1.3;
  6. comment  @ * @;
  7.  
  8.  
  9. 1.3
  10. date     91.03.02.14.23.35;  author gtoal;  state Exp;
  11. branches ;
  12. next     1.2;
  13.  
  14. 1.2
  15. date     91.03.02.13.59.21;  author gtoal;  state Exp;
  16. branches ;
  17. next     1.1;
  18.  
  19. 1.1
  20. date     91.03.02.13.56.04;  author gtoal;  state Exp;
  21. branches ;
  22. next     ;
  23.  
  24.  
  25. desc
  26. @Initial release
  27. @
  28.  
  29.  
  30. 1.3
  31. log
  32. @A constant expression was overflowing at compile time
  33. @
  34. text
  35. @/* output.c --- saving and transferring data.  */
  36.  
  37. #include "d2rd.h"
  38. #include <stdio.h>
  39. #include <stdarg.h>
  40. #include <string.h>
  41. #include <stdlib.h>
  42. #include "kernel.h"
  43. #include "output.h"
  44. #include "visdelay.h"
  45. #include "font.h"
  46. #include "flex.h"
  47.  
  48. #define VERT_SIZE (int)(A4_HEIGHT*180*256)   /* height of page in Draw internal units */
  49.  
  50. /* Forward declarations.  */
  51.  
  52. void output_sprite (outputter, FILE *);
  53. void output_draw (outputter, FILE *);
  54. size_t ram_write (const void *, size_t, size_t, FILE *);
  55.  
  56. static char *my_buf;
  57. static char *your_buf;
  58. static int buf_size;
  59. static int buf_pos;
  60. static wimp_t dest_task;
  61. static int your_ref;
  62.  
  63.  
  64. void
  65. send_buf (int size)
  66. {
  67.   wimp_msgstr msg;
  68.   wimp_eventstr b;
  69.  
  70.   msg.hdr.action = wimp_MRAMTRANSMIT;
  71.   msg.hdr.your_ref = your_ref;
  72.   msg.hdr.size = sizeof (wimp_msgstr);
  73.   msg.data.ramtransmit.addr = your_buf;
  74.   msg.data.ramtransmit.nbyteswritten = size;
  75.   wimpt_noerr (wimp_transferblock (wimpt_task (), my_buf, dest_task, your_buf, size));
  76.   if (size != buf_size)
  77.     wimpt_noerr (wimp_sendmessage (wimp_ESEND, &msg, dest_task));
  78.   else
  79.     {
  80.       wimpt_noerr (wimp_sendmessage (wimp_ESENDWANTACK, &msg, dest_task));
  81.       for (;;)
  82.         {
  83.           wimpt_noerr (wimp_poll (0x1973, &b));
  84.           switch (b.e)
  85.             {
  86.             case wimp_ESEND:
  87.             case wimp_ESENDWANTACK:
  88.               if (b.data.msg.hdr.your_ref == msg.hdr.my_ref)
  89.                 {
  90.                   dest_task = b.data.msg.hdr.task;                 /* paranoid */
  91.                   your_ref = b.data.msg.hdr.my_ref;
  92.                   your_buf = b.data.msg.data.ramfetch.addr;
  93.                   buf_size = b.data.msg.data.ramfetch.nbytes;
  94.                   my_buf = realloc (my_buf, buf_size);
  95.                   return;
  96.                 }
  97.               else
  98.                 tfatal ("EXPORT FAILED!");
  99. #if 0
  100.                 tfatal ("References fail (%d, %d, %d, %d)", msg.hdr.my_ref, msg.hdr.your_ref, b.data.msg.hdr.my_ref, b.data.msg.hdr.your_ref);
  101. #endif            
  102.             case wimp_EACK:
  103.               fatal ("RAM transfer failed");
  104.               break;
  105.         
  106.             default:
  107. #if 0
  108.               fatal ("unwanted event: %d", b.e);
  109. #endif
  110.               continue;
  111.             }
  112.           break;
  113.         }    
  114.     }
  115. } /* send_buf */
  116.  
  117.  
  118.  
  119. void
  120. output_send (wimp_msgstr *m)
  121. {
  122.   FILE *f = NULL;
  123.  
  124.   your_buf = m->data.ramfetch.addr;
  125.   buf_size = m->data.ramfetch.nbytes;
  126.   dest_task = m->hdr.task;
  127.   your_ref = m->hdr.my_ref;
  128.  
  129.   /* If the buffer on the other size is large enough, we can get rid of the
  130.      sprite at once.  */
  131.  
  132.   if (saveas_filetype == 0xff9 && buf_size > flex_size ((flex_ptr) &which_menu->area))
  133.     {
  134.       buf_pos = 0;
  135.       buf_size = 0;
  136.       my_buf = (char *) &which_menu->area->number;
  137.       send_buf (flex_size ((flex_ptr) &which_menu->area) - 4);
  138.       return;
  139.     }
  140.  
  141.   my_buf = xmalloc (buf_size);
  142.   buf_pos = 0;
  143.  
  144.   visdelay_begin ();
  145.  
  146.   switch (saveas_filetype)
  147.     {
  148.     case 0xff9:
  149.       ram_write (&which_menu->area->number, 1, which_menu->area->size - 4, f);
  150.       break;
  151.     case 0xaff:
  152.       output_draw (&ram_write, f);
  153.       break;
  154.     default:
  155.       tfatal ("But I have never heard of filetype 0x%x!", saveas_filetype);
  156.       break;
  157.     }
  158.  
  159.   wimp_create_menu ((wimp_menustr *) -1, 0, 0);
  160.   send_buf (buf_pos);
  161.   visdelay_end ();
  162.   free (my_buf);
  163. } /* saveas_send */
  164.  
  165.  
  166.  
  167. size_t
  168. ram_write (const void *b, size_t size, size_t nmemb, FILE *f)
  169. {
  170.   int n = size * nmemb, ret = n;
  171.   char *from = (char *)b;
  172.  
  173.   f = f;
  174.  
  175.   for (;;)
  176.     {
  177.       if (buf_pos + n < buf_size)
  178.         {
  179.           for (; n; buf_pos++, from++, n--)
  180.             my_buf[buf_pos] = *from;
  181.           break;
  182.         }
  183.       for (; buf_pos < buf_size; buf_pos++, from++, n--)
  184.         my_buf[buf_pos] = *from;
  185.       send_buf (buf_size);
  186.       buf_pos = 0;
  187.     }
  188.   return (ret);
  189. } /* ram_write */
  190.  
  191.  
  192. void
  193. output_saveas (char *name)
  194. {
  195.   char cmd[300];
  196.   FILE *f;
  197.  
  198.   wimp_create_menu ((wimp_menustr *)-1, 0, 0);
  199.   visdelay_begin ();
  200.  
  201.   f = fopen (name, "wb");
  202.   if (f == NULL)
  203.     {
  204.       fatal ("Can't open file `%s'.", name);
  205.       return;
  206.     }
  207.  
  208.   switch (saveas_filetype)
  209.     {
  210.     case 0xff9:
  211.       fwrite (&which_menu->area->number, 1, which_menu->area->size - 4, f);
  212.       sprintf (cmd, "settype %s ff9", name);
  213.       break;
  214.  
  215.     case 0xaff:
  216.       output_draw (&fwrite, f);
  217.       sprintf (cmd, "settype %s aff", name);
  218.       break;
  219.  
  220.     default:
  221.       tfatal ("But I have never heard of filetype 0x%x!", saveas_filetype);
  222.       break;
  223.     }
  224.   fclose (f);
  225.   _kernel_oscli (cmd);
  226.   visdelay_end ();
  227. } /* output_saveas */
  228.  
  229. /* The routines below are concerned with outputting a draw format file.  */
  230.  
  231. static int
  232. write_n (FILE *f, outputter put_out, int n, ...)
  233. {
  234.   va_list ap;
  235.   int *a, i;
  236.  
  237.   va_start (ap, n);
  238.   a = (int *) xmalloc (n * sizeof (int));
  239.   for (i = 0; i < n; i++)
  240.     a[i] = va_arg (ap, int);
  241.   va_end (ap);
  242.   i = put_out (a, sizeof (int), n, f);
  243.   free (a);
  244.   return (i);
  245. } /* write_n */
  246.  
  247.  
  248.  
  249. void
  250. output_draw (outputter put_out, FILE *f)
  251. {
  252.   struct display *w = which_menu;
  253.   struct page *p = w->page;
  254.   struct dvi_file *df = w->file;
  255.   struct text *txt;
  256.   struct rule *rl;
  257.   int *dvi_to_font = xcalloc (sizeof (int), 256);
  258.   int *font_to_dvi = xcalloc (sizeof (int), 256);
  259.   int max_font = 1, size = 0, rsize, i, j, k, l, t, x, y;
  260.   char *s;
  261.  
  262.   /*
  263.   ** hor_offset holds the horizontal offset for all objects, in
  264.   ** millipoints.  Usually 1in, or 72000 millipoints.
  265.   */
  266.   int hor_offset = w->hor_offset;
  267.  
  268.   /*
  269.   ** ver_offset holds the distance from the bottom of the page to
  270.   ** the offset point, normally 1in from the top edge.  This is
  271.   ** held in millipoints.
  272.   */
  273.   int ver_offset = w->ver_size - w->ver_offset;
  274.  
  275.   /* Output DrawFile header.  */
  276.  
  277.   put_out ("Draw", 1, 4, f);
  278.   write_n (f, put_out, 2, 201, 0);
  279.   put_out ("Preview     ", 1, 12, f);
  280.  
  281. #define VS (11.69*180.0*256.0*(10000.0 / 14142.0))
  282.   write_n (f, put_out, 4, 0, 0, VS, VERT_SIZE); /* avoid constant-overflow! */
  283.  
  284.   /* Build and output the font information object.  */
  285.  
  286.   txt = p->texts;
  287.   for (t = 0; t < p->text_max; t++, txt++)
  288.     if (dvi_to_font[txt->font] == 0)
  289.       {
  290.         font_to_dvi[max_font] = txt->font;
  291.         dvi_to_font[txt->font] = max_font;
  292.         size += 2 + strlen (df->fonts[txt->font]->name);
  293.         max_font++;
  294.       }
  295.   if (size)
  296.     {
  297.       rsize = (size + 3) & ~3;
  298.       write_n (f, put_out, 2, 0, rsize + 8);
  299.       for (i = 1; i < max_font; i++)
  300.         {
  301.           s = df->fonts[font_to_dvi[i]]->name;
  302.           put_out (&i, 1, 1, f);
  303.           put_out (s, 1, 1 + strlen (s), f);
  304.         }
  305.       l = 0;
  306.       for (i = size; i < rsize; i++)
  307.         put_out (&l, 1, 1, f);
  308.     }
  309.  
  310.  
  311.   /* Output the text blobs.  */
  312.  
  313.   for (t = 0, txt = p->texts; t < p->text_max; t++, txt++)
  314.     {
  315.       l = strlen (&p->chars[txt->text]);
  316.       i = (l + 4) & ~3;
  317.       size = 40 * df->fonts[txt->font]->size;
  318.       font_converttoos (hor_offset + txt->x, ver_offset - txt->y, &x, &y);
  319.       font_converttoos (hor_offset + txt->rx, ver_offset - txt->ty, &j, &k);
  320.  
  321.       x *= 256, y *= 256, j *= 256, k *= 256;
  322.  
  323.       write_n (f, put_out, 4, 1, 52 + i, x, y);
  324.       write_n (f, put_out, 2, j, k);
  325.       write_n (f, put_out, 7, 0, 0xffffff00, dvi_to_font[txt->font], size, size, x, y);
  326.       put_out (&p->chars[txt->text], 1, l, f);
  327.       k = 0;
  328.       for (j = l; j < i; j++)
  329.         put_out (&k, 1, 1, f);
  330.     }
  331.  
  332.   /* Output rules.  */
  333.  
  334.   for (t = 0, rl = p->rules; t < p->rule_max; t++, rl++)
  335.     {
  336.       font_converttoos ((hor_offset + rl->x) * 256,
  337.                         (ver_offset - rl->y) * 256, &x, &y);
  338.       font_converttoos (rl->w * 256, rl->h * 256, &j, &k);
  339.  
  340.       write_n (f, put_out, 6, 2, 24 + 11 * 4, x, y, x + j, y + k);
  341.       write_n (f, put_out, 11, -1, 0, k, 0x20100042, 2, x, y+k/2, 8, x + j, y+k/2, 0);
  342.     }
  343. } /* output_draw */
  344.  
  345. /* EOF */
  346. @
  347.  
  348.  
  349. 1.2
  350. log
  351. @IAY's upgrade
  352. @
  353. text
  354. @d246 3
  355. a248 1
  356.   write_n (f, put_out, 4, 0, 0, VERT_SIZE * 10000 / 14142, VERT_SIZE);
  357. @
  358.  
  359.  
  360. 1.1
  361. log
  362. @Initial revision
  363. @
  364. text
  365. @d14 1
  366. a14 2
  367. #define VERT_SIZE   5297385/11        /* Should be: 29.2 / 2.54 * 72 * 640 */
  368. #define ONE_INCH    (180 * 256)
  369. a15 1
  370.  
  371. a88 1
  372.   int i;
  373. d201 1
  374. a201 1
  375.   int *a, i, j;
  376. d228 13
  377. a247 1
  378.  
  379. d282 2
  380. a283 4
  381.       font_converttoos ((int) (txt->x * 95.0 / 90.0),
  382.                         (int) ((((w->ver_size - w->ver_offset) * 72000.0) - 95.0 * txt->y) / 90.0), &x, &y);
  383.       font_converttoos ((int) (txt->rx * 95.0 / 90.0),
  384.                         (int) ((((w->ver_size - w->ver_offset) * 72000.0) - 95.0 * txt->ty) / 90.0), &j, &k);
  385. d289 1
  386. a289 1
  387.       write_n (f, put_out, 7, 0, 0xffffff00, dvi_to_font[txt->font], (int) (size * 95.0 / 90.0), (int) (size * 95.0 / 90.0), x, y);
  388. d300 3
  389. a302 3
  390.       font_converttoos ((int) (rl->x * 256.0 * 95.0 / 90.0),
  391.                         (int) ((((w->ver_size - w->ver_offset) * 72000.0) - 95.0 * rl->y) * 256.0 / 90.0), &x, &y);
  392.       font_converttoos ((int) (rl->w * 95.0 * 256.0 / 90.0), (int) (rl->h * 95.0 * 256.0 / 90.0), &j, &k);
  393. d305 1
  394. a305 1
  395.       write_n (f, put_out, 11, -1, 0, k, 0x20100042, 2, x, y, 8, x + j, y, 0);
  396. @
  397.